/**
 * 维护”企业微信主体白名单“，开启白名单后，只有指定主体的企业微信允许登录
 */
import { getLogger, Service } from '@gnlab/utils'
import { MemSubject } from '@gnlab/utils/rx'
import type { Services } from '@/services'
import { API } from '@/services/common/api'

const logger = getLogger('services/features/corp-whitelist')

export interface WhitelistCorp {
  id: number
  corpid: string
  desc: string
}

export class CorpWhitelistSrv extends Service<Services> {
  private get auth() {
    return this.services.auth
  }

  // null 代表数据还未载入完成
  enable = new MemSubject<null | boolean>(null)
  list = new MemSubject<null | WhitelistCorp[]>(null)

  registered() {
    void Promise.resolve(this.auth.accountId).then(() => {
      void this.getStatus()
      void this.load()
    })
  }

  /**
   * 判断指定企业微信主体能否通过白名单检查
   * 返回 null 代表白名单尚未载入完成或载入失败
   */
  check(corpid: string) {
    const enable = this.enable.value
    const list = this.list.value

    if (enable === false) return true // enabel 为 false 时，不考虑 list，即使 list 为 null 也视为通过白名单检查（因为白名单压根没启用）
    if (enable === null || list === null) return null
    return !!list.find(item => item.corpid === corpid)
  }

  async getStatus() {
    const res = await API<{ IsLoginWhitelist: boolean }>('/Config/GetConfig')
    if (res.success) {
      this.enable.next(res.data.IsLoginWhitelist)
    } else {
      void logger.warn('获取登录白名单状态失败', res.error)
    }
  }

  async updateStatus(enable: boolean) {
    this.enable.next(enable)
    const res = await API('/Config/SaveIsLoginWhitelist', { data: { IsLoginWhitelist: enable } })
    return res.success ? true : res.error
  }

  async load() {
    interface RespWhiteList {
      Id: number
      CorpId: string
      Desc: string
    }
    const res = await API<RespWhiteList[]>('/Config/GetLoginWhitelist')
    if (res.success) {
      const list = res.data.map(raw => ({
        id: raw.Id,
        corpid: raw.CorpId,
        desc: raw.Desc,
      }))
      this.list.next(list)
    } else {
      logger.warn('登录白名单加载失败', res.error)
    }
  }

  async addOrUpdate(data: Omit<WhitelistCorp, 'id'> & { id?: number }) {
    const res = await API('/Config/SaveLoginWhitelist', {
      data: {
        Id: data.id,
        CorpId: data.corpid,
        Desc: data.desc,
      },
    })
    void this.load()
    if (res.success) {
      return true
    } else {
      logger.warn(`登录白名单保存失败：${res.error}`)
      return res.error
    }
  }

  async remove(id: number) {
    const res = await API('/Config/RemoveLoginWhitelist', { data: { Id: id } })
    void this.load()
    if (res.success) {
      return true
    } else {
      logger.warn(`删除白名单失败：${res.error}`)
      return res.error
    }
  }
}
